package com.fastCms.business.bim.manage.impl;

import com.fastCms.business.frame.constant.CommonConst;
import com.fastCms.business.frame.constant.ResultCodeConst;
import com.fastCms.business.bim.daos.AreaDeviceRelMapper;
import com.fastCms.business.bim.manage.AreaManageService;
import com.fastCms.business.bim.pojo.entity.Area;
import com.fastCms.business.bim.pojo.entity.AreaDeviceRel;
import com.fastCms.business.bim.pojo.po.AreaDeviceRelPO;
import com.fastCms.business.bim.pojo.po.AreaSavePO;
import com.fastCms.business.bim.pojo.vo.AreaVO;
import com.fastCms.business.bim.pojo.vo.DeviceInfoVO;
import com.fastCms.business.bim.service.AreaDeviceRelService;
import com.fastCms.business.bim.service.AreaService;
import com.fastCms.business.frame.response.ApiResponse;
import com.fastCms.business.frame.response.ResponseUtil;
import com.fastCms.business.frame.utils.CommonsUtil;
import lombok.extern.slf4j.Slf4j;
import org.apache.commons.collections.CollectionUtils;
import org.springframework.beans.BeanUtils;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.stereotype.Component;
import org.springframework.transaction.annotation.Transactional;

import java.util.ArrayList;
import java.util.LinkedHashMap;
import java.util.List;
import java.util.stream.Collectors;

@Transactional(rollbackFor = Exception.class)
@Component
@Slf4j
public class AreaManageServiceImpl implements AreaManageService {

    @Autowired
    private AreaService areaServiceImpl;

    @Autowired
    private AreaDeviceRelMapper areaDeviceRelMapper;

    @Autowired
    private AreaDeviceRelService areaDeviceRelServiceImpl;

    @Override
    public ApiResponse<Boolean> saveOrUpdateArea(AreaSavePO savePO) {
        if (null != savePO.getId()) {
            Area area = areaServiceImpl.findById(savePO.getId());
            if (null == area) {
                return ResponseUtil.fail("数据不存在");
            }
            BeanUtils.copyProperties(savePO, area);
            areaServiceImpl.updateById(area);
        } else {
            Area area = new Area();
            BeanUtils.copyProperties(savePO, area);
            CommonsUtil.initEntity(area);
            areaServiceImpl.save(area);
        }
        return ResponseUtil.success(true);
    }

    @Override
    public ApiResponse<AreaVO> getDetail(Integer areaId) {

        Area area = areaServiceImpl.findById(areaId);
        if (null != area) {
            return ResponseUtil.success(area);
        }
        return ResponseUtil.fail("数据不存在");
    }

    @Override
    public ApiResponse<String> getFullAreaName(Integer areaId) {
        String areaName = getAreaName("", areaId);
        return ResponseUtil.success(areaName);

    }

    private String getAreaName(String areaName, Integer areaId) {
        Area area = areaServiceImpl.findById(areaId);
        if (null == area.getPid()) {
            return areaName;
        }
        String areaParent = getAreaName(areaName + area.getAreaName(), area.getPid());
        return areaParent;
    }


    @Override
    public ApiResponse<Boolean> delete(Integer areaId) {
        Area area = areaServiceImpl.findById(areaId);
        if (null == area) {
            return ResponseUtil.fail("数据不存在");
        }
        area.setState(CommonConst.STATE.INVALID);
        boolean b = areaServiceImpl.updateById(area);
        return ResponseUtil.success(b);
    }

    @Override
    public ApiResponse<Boolean> relDevice(AreaDeviceRelPO deviceRelPO) {
        Integer areaId = deviceRelPO.getAreaId();
        List<Integer> deviceIds = deviceRelPO.getDeviceIds();
        for (Integer deviceId : deviceIds) {
            AreaDeviceRel areaDeviceRel = areaDeviceRelServiceImpl.findByAreaIdAndDeviceId(areaId, deviceId);
            if (areaDeviceRel != null) {
                return ResponseUtil.fail(ResultCodeConst.PARAM_ERROR, "设备ID = " + deviceId + "的设备已在该区域!");
            }
        }
//        List<AreaDeviceRel> devicedRels = areaDeviceRelMapper.findByAreaIdAndDeviceIdIn(deviceRelPO);
        List<AreaDeviceRel> deviceRels = deviceIds.stream().map(deviceId -> {
            AreaDeviceRel areaDeviceRel = new AreaDeviceRel();
            CommonsUtil.initEntity(areaDeviceRel);
            areaDeviceRel.setAreaId(areaId);
            areaDeviceRel.setDeviceId(deviceId);
            return areaDeviceRel;
        }).collect(Collectors.toList());
        boolean b = areaDeviceRelServiceImpl.saveOrUpdateBatch(deviceRels);
        return ResponseUtil.success(b);
    }

    @Override
    public ApiResponse<List<DeviceInfoVO>> getDevicesByAreaId(Integer areaId) {
        List<DeviceInfoVO> devices = areaDeviceRelMapper.getDevicesByAreaId(areaId);
        return ResponseUtil.success(devices);
    }

    @Override
    public ApiResponse<Boolean> deleteDeviceRel(Integer areaId, Integer deviceId) {
        AreaDeviceRel areaDeviceRel = areaDeviceRelServiceImpl.findByAreaIdAndDeviceId(areaId, deviceId);
        if (null != areaDeviceRel) {
            areaDeviceRel.setState(CommonConst.STATE.INVALID);
            boolean b = areaDeviceRelServiceImpl.updateById(areaDeviceRel);
            return ResponseUtil.success(b);
        }
        return ResponseUtil.fail("数据不存在");
    }

    @Override
    public ApiResponse<List<AreaVO>> areaList() {
        List<Area> areas = areaServiceImpl.findValidAll();
        List<AreaVO> areaTree = getAreaTree(areas);
        return ResponseUtil.success(areaTree);
    }

    @Override
    public ApiResponse<List<AreaVO>> apiAreaList() {
        List<Area> areas = areaServiceImpl.findValidAll();
        return ResponseUtil.success(areas);
    }

    /**
     * @Description 获取菜单树状结构
     * @Param [cloudMenus]
     * @Date 2019/3/11 下午2:28 lsquan
     */
    public List<AreaVO> getAreaTree(List<Area> areaList) {

        // 源数据转换VO
        List<AreaVO> cloudMenuVOS = areaList.stream().map(menu -> {
            AreaVO cloudMenuVO = new AreaVO();
            BeanUtils.copyProperties(menu, cloudMenuVO);
            return cloudMenuVO;
        }).collect(Collectors.toList());

        // list->map
        LinkedHashMap<Integer, AreaVO> cloudMenuMap = new LinkedHashMap<>();
        for (AreaVO cloudMenuVO : cloudMenuVOS) {
            cloudMenuMap.put(cloudMenuVO.getId(), cloudMenuVO);
        }
        // 菜单数据组装
        List<AreaVO> nodeTrees = new ArrayList<>();
        for (Integer id : cloudMenuMap.keySet()) {
            AreaVO cloudMenu = cloudMenuMap.get(id);
            Integer parentId = cloudMenu.getPid();
            if (null == parentId || !cloudMenuMap.containsKey(parentId)) {
                nodeTrees.add(cloudMenu);
            } else {
                AreaVO parentTreeNode = cloudMenuMap.get(parentId);
                if (CollectionUtils.isEmpty(parentTreeNode.getChildArea())) {
                    parentTreeNode.setChildArea(new ArrayList<>());
                }
                parentTreeNode.getChildArea().add(cloudMenu);
            }
        }
        // 取根节点的树
        nodeTrees =
            nodeTrees.stream().filter(sysMenu -> null == sysMenu.getPid()).collect(Collectors.toList());
        return nodeTrees;
    }


}
